package cn.sh.yhk.mapper.basic;

import cn.sh.yhk.model.basic.SUser;
import cn.sh.yhk.model.basic.SUserExample;
import cn.sh.yhk.model.basic.SUserExample.Criteria;
import cn.sh.yhk.model.basic.SUserExample.Criterion;
import org.apache.ibatis.jdbc.SQL;

import java.util.List;
import java.util.Map;

public class SUserSqlProvider {

    public String countByExample(SUserExample example) {
        SQL sql = new SQL();
        sql.SELECT("count(*)").FROM("s_user");
        applyWhere(sql, example, false);
        return sql.toString();
    }

    public String deleteByExample(SUserExample example) {
        SQL sql = new SQL();
        sql.DELETE_FROM("s_user");
        applyWhere(sql, example, false);
        return sql.toString();
    }

    public String insertSelective(SUser record) {
        SQL sql = new SQL();
        sql.INSERT_INTO("s_user");

        if (record.getUserId() != null) {
            sql.VALUES("user_id", "#{userId,jdbcType=BIGINT}");
        }

        if (record.getUserAccount() != null) {
            sql.VALUES("user_account", "#{userAccount,jdbcType=VARCHAR}");
        }

        if (record.getPassword() != null) {
            sql.VALUES("password", "#{password,jdbcType=VARCHAR}");
        }


        if (record.getUserName() != null) {
            sql.VALUES("user_name", "#{userName,jdbcType=VARCHAR}");
        }

        if (record.getUserSearchName() != null) {
            sql.VALUES("user_search_name", "#{userSearchName,jdbcType=VARCHAR}");
        }

        if (record.getMobileNumber() != null) {
            sql.VALUES("mobile_number", "#{mobileNumber,jdbcType=VARCHAR}");
        }

        if (record.getTimeZone() != null) {
            sql.VALUES("time_zone", "#{timeZone,jdbcType=VARCHAR}");
        }

        if (record.getSex() != null) {
            sql.VALUES("sex", "#{sex,jdbcType=VARCHAR}");
        }

        if (record.getIdCardCd() != null) {
            sql.VALUES("id_card_cd", "#{idCardCd,jdbcType=VARCHAR}");
        }

        if (record.getCountryCd() != null) {
            sql.VALUES("country_cd", "#{countryCd,jdbcType=VARCHAR}");
        }

        if (record.getZipCode() != null) {
            sql.VALUES("zip_code", "#{zipCode,jdbcType=VARCHAR}");
        }

        if (record.getAddress1() != null) {
            sql.VALUES("address1", "#{address1,jdbcType=VARCHAR}");
        }

        if (record.getAddress2() != null) {
            sql.VALUES("address2", "#{address2,jdbcType=VARCHAR}");
        }

        if (record.getAddress3() != null) {
            sql.VALUES("address3", "#{address3,jdbcType=VARCHAR}");
        }

        if (record.getTelephoneNumber() != null) {
            sql.VALUES("telephone_number", "#{telephoneNumber,jdbcType=VARCHAR}");
        }

        if (record.getRemark() != null) {
            sql.VALUES("remark", "#{remark,jdbcType=VARCHAR}");
        }

        if (record.getActivity() != null) {
            sql.VALUES("activity", "#{activity,jdbcType=VARCHAR}");
        }

        if (record.getLocked() != null) {
            sql.VALUES("locked", "#{locked,jdbcType=INTEGER}");
        }

        if (record.getResetPassword() != null) {
            sql.VALUES("reset_password", "#{resetPassword,jdbcType=INTEGER}");
        }

        if (record.getSortKey() != null) {
            sql.VALUES("sort_key", "#{sortKey,jdbcType=BIGINT}");
        }

        if (record.getCreateAccount() != null) {
            sql.VALUES("create_account", "#{createAccount,jdbcType=VARCHAR}");
        }

        if (record.getModifyAccount() != null) {
            sql.VALUES("modify_account", "#{modifyAccount,jdbcType=VARCHAR}");
        }

        if (record.getCreateTimestamp() != null) {
            sql.VALUES("create_timestamp", "#{createTimestamp,jdbcType=TIMESTAMP}");
        }

        if (record.getModifyTimestamp() != null) {
            sql.VALUES("modify_timestamp", "#{modifyTimestamp,jdbcType=TIMESTAMP}");
        }

        if (record.getLastLoginTimestamp() != null) {
            sql.VALUES("last_login_timestamp", "#{lastLoginTimestamp,jdbcType=TIMESTAMP}");
        }
        if (record.getEmail() != null) {
            sql.VALUES("email", "#{email,jdbcType=VARCHAR}");
        }
        return sql.toString();
    }

    public String selectByExample(SUserExample example) {
        SQL sql = new SQL();
        if (example != null && example.isDistinct()) {
            sql.SELECT_DISTINCT("user_id");
        } else {
            sql.SELECT("user_id");
        }
        sql.SELECT("user_account");
        sql.SELECT("password");
        sql.SELECT("user_name");
        sql.SELECT("user_search_name");
        sql.SELECT("mobile_number");
        sql.SELECT("time_zone");
        sql.SELECT("sex");
        sql.SELECT("id_card_cd");
        sql.SELECT("country_cd");
        sql.SELECT("zip_code");
        sql.SELECT("address1");
        sql.SELECT("address2");
        sql.SELECT("address3");
        sql.SELECT("telephone_number");
        sql.SELECT("remark");
        sql.SELECT("activity");
        sql.SELECT("locked");
        sql.SELECT("reset_password");
        sql.SELECT("sort_key");
        sql.SELECT("create_account");
        sql.SELECT("modify_account");
        sql.SELECT("create_timestamp");
        sql.SELECT("modify_timestamp");
        sql.SELECT("last_login_timestamp");
        sql.SELECT("email");
        sql.FROM("s_user");
        applyWhere(sql, example, false);

        if (example != null && example.getOrderByClause() != null) {
            sql.ORDER_BY(example.getOrderByClause());
        }

        return sql.toString();
    }

    public String updateByExampleSelective(Map<String, Object> parameter) {
        SUser record = (SUser) parameter.get("record");
        SUserExample example = (SUserExample) parameter.get("example");

        SQL sql = new SQL();
        sql.UPDATE("s_user");
        if (record.getSessionId() != null) {
            sql.SET("session_id = #{record.sessionId,jdbcType=VARCHAR}");
        }
        if (record.getUserId() != null) {
            sql.SET("user_id = #{record.userId,jdbcType=BIGINT}");
        }

        if (record.getUserAccount() != null) {
            sql.SET("user_account = #{record.userAccount,jdbcType=VARCHAR}");
        }

        if (record.getPassword() != null) {
            sql.SET("password = #{record.password,jdbcType=VARCHAR}");
        }


        if (record.getUserName() != null) {
            sql.SET("user_name = #{record.userName,jdbcType=VARCHAR}");
        }

        if (record.getUserSearchName() != null) {
            sql.SET("user_search_name = #{record.userSearchName,jdbcType=VARCHAR}");
        }

        if (record.getMobileNumber() != null) {
            sql.SET("mobile_number = #{record.mobileNumber,jdbcType=VARCHAR}");
        }

        if (record.getTimeZone() != null) {
            sql.SET("time_zone = #{record.timeZone,jdbcType=VARCHAR}");
        }

        if (record.getSex() != null) {
            sql.SET("sex = #{record.sex,jdbcType=VARCHAR}");
        }

        if (record.getIdCardCd() != null) {
            sql.SET("id_card_cd = #{record.idCardCd,jdbcType=VARCHAR}");
        }

        if (record.getCountryCd() != null) {
            sql.SET("country_cd = #{record.countryCd,jdbcType=VARCHAR}");
        }

        if (record.getZipCode() != null) {
            sql.SET("zip_code = #{record.zipCode,jdbcType=VARCHAR}");
        }

        if (record.getAddress1() != null) {
            sql.SET("address1 = #{record.address1,jdbcType=VARCHAR}");
        }

        if (record.getAddress2() != null) {
            sql.SET("address2 = #{record.address2,jdbcType=VARCHAR}");
        }

        if (record.getAddress3() != null) {
            sql.SET("address3 = #{record.address3,jdbcType=VARCHAR}");
        }

        if (record.getTelephoneNumber() != null) {
            sql.SET("telephone_number = #{record.telephoneNumber,jdbcType=VARCHAR}");
        }

        if (record.getRemark() != null) {
            sql.SET("remark = #{record.remark,jdbcType=VARCHAR}");
        }

        if (record.getActivity() != null) {
            sql.SET("activity = #{record.activity,jdbcType=VARCHAR}");
        }

        if (record.getLocked() != null) {
            sql.SET("locked = #{record.locked,jdbcType=INTEGER}");
        }

        if (record.getResetPassword() != null) {
            sql.SET("reset_password = #{record.resetPassword,jdbcType=INTEGER}");
        }

        if (record.getSortKey() != null) {
            sql.SET("sort_key = #{record.sortKey,jdbcType=BIGINT}");
        }

        if (record.getCreateAccount() != null) {
            sql.SET("create_account = #{record.createAccount,jdbcType=VARCHAR}");
        }

        if (record.getModifyAccount() != null) {
            sql.SET("modify_account = #{record.modifyAccount,jdbcType=VARCHAR}");
        }

        if (record.getCreateTimestamp() != null) {
            sql.SET("create_timestamp = #{record.createTimestamp,jdbcType=TIMESTAMP}");
        }

        if (record.getModifyTimestamp() != null) {
            sql.SET("modify_timestamp = #{record.modifyTimestamp,jdbcType=TIMESTAMP}");
        }

        if (record.getLastLoginTimestamp() != null) {
            sql.SET("last_login_timestamp = #{record.lastLoginTimestamp,jdbcType=TIMESTAMP}");
        }
        if (record.getEmail() != null) {
            sql.SET("email = #{record.email,jdbcType=VARCHAR}");
        }

        applyWhere(sql, example, true);
        return sql.toString();
    }

    public String updateByExample(Map<String, Object> parameter) {
        SQL sql = new SQL();
        sql.UPDATE("s_user");

        sql.SET("user_id = #{record.userId,jdbcType=BIGINT}");
        sql.SET("user_account = #{record.userAccount,jdbcType=VARCHAR}");
        sql.SET("password = #{record.password,jdbcType=VARCHAR}");
        sql.SET("user_name = #{record.userName,jdbcType=VARCHAR}");
        sql.SET("user_search_name = #{record.userSearchName,jdbcType=VARCHAR}");
        sql.SET("mobile_number = #{record.mobileNumber,jdbcType=VARCHAR}");
        sql.SET("time_zone = #{record.timeZone,jdbcType=VARCHAR}");
        sql.SET("sex = #{record.sex,jdbcType=VARCHAR}");
        sql.SET("id_card_cd = #{record.idCardCd,jdbcType=VARCHAR}");
        sql.SET("country_cd = #{record.countryCd,jdbcType=VARCHAR}");
        sql.SET("zip_code = #{record.zipCode,jdbcType=VARCHAR}");
        sql.SET("address1 = #{record.address1,jdbcType=VARCHAR}");
        sql.SET("address2 = #{record.address2,jdbcType=VARCHAR}");
        sql.SET("address3 = #{record.address3,jdbcType=VARCHAR}");
        sql.SET("telephone_number = #{record.telephoneNumber,jdbcType=VARCHAR}");
        sql.SET("remark = #{record.remark,jdbcType=VARCHAR}");
        sql.SET("activity = #{record.activity,jdbcType=VARCHAR}");
        sql.SET("locked = #{record.locked,jdbcType=INTEGER}");
        sql.SET("reset_password = #{record.resetPassword,jdbcType=INTEGER}");
        sql.SET("sort_key = #{record.sortKey,jdbcType=BIGINT}");
        sql.SET("create_account = #{record.createAccount,jdbcType=VARCHAR}");
        sql.SET("modify_account = #{record.modifyAccount,jdbcType=VARCHAR}");
        sql.SET("create_timestamp = #{record.createTimestamp,jdbcType=TIMESTAMP}");
        sql.SET("modify_timestamp = #{record.modifyTimestamp,jdbcType=TIMESTAMP}");
        sql.SET("last_login_timestamp = #{record.lastLoginTimestamp,jdbcType=TIMESTAMP}");
        sql.SET("email = #{record.email,jdbcType=VARCHAR}");

        SUserExample example = (SUserExample) parameter.get("example");
        applyWhere(sql, example, true);
        return sql.toString();
    }

    protected void applyWhere(SQL sql, SUserExample example, boolean includeExamplePhrase) {
        if (example == null) {
            return;
        }

        String parmPhrase1;
        String parmPhrase1_th;
        String parmPhrase2;
        String parmPhrase2_th;
        String parmPhrase3;
        String parmPhrase3_th;
        if (includeExamplePhrase) {
            parmPhrase1 = "%s #{example.oredCriteria[%d].allCriteria[%d].value}";
            parmPhrase1_th = "%s #{example.oredCriteria[%d].allCriteria[%d].value,typeHandler=%s}";
            parmPhrase2 = "%s #{example.oredCriteria[%d].allCriteria[%d].value} and #{example.oredCriteria[%d].criteria[%d].secondValue}";
            parmPhrase2_th = "%s #{example.oredCriteria[%d].allCriteria[%d].value,typeHandler=%s} and #{example.oredCriteria[%d].criteria[%d].secondValue,typeHandler=%s}";
            parmPhrase3 = "#{example.oredCriteria[%d].allCriteria[%d].value[%d]}";
            parmPhrase3_th = "#{example.oredCriteria[%d].allCriteria[%d].value[%d],typeHandler=%s}";
        } else {
            parmPhrase1 = "%s #{oredCriteria[%d].allCriteria[%d].value}";
            parmPhrase1_th = "%s #{oredCriteria[%d].allCriteria[%d].value,typeHandler=%s}";
            parmPhrase2 = "%s #{oredCriteria[%d].allCriteria[%d].value} and #{oredCriteria[%d].criteria[%d].secondValue}";
            parmPhrase2_th = "%s #{oredCriteria[%d].allCriteria[%d].value,typeHandler=%s} and #{oredCriteria[%d].criteria[%d].secondValue,typeHandler=%s}";
            parmPhrase3 = "#{oredCriteria[%d].allCriteria[%d].value[%d]}";
            parmPhrase3_th = "#{oredCriteria[%d].allCriteria[%d].value[%d],typeHandler=%s}";
        }

        StringBuilder sb = new StringBuilder();
        List<Criteria> oredCriteria = example.getOredCriteria();
        boolean firstCriteria = true;
        for (int i = 0; i < oredCriteria.size(); i++) {
            Criteria criteria = oredCriteria.get(i);
            if (criteria.isValid()) {
                if (firstCriteria) {
                    firstCriteria = false;
                } else {
                    sb.append(" or ");
                }

                sb.append('(');
                List<Criterion> criterions = criteria.getAllCriteria();
                boolean firstCriterion = true;
                for (int j = 0; j < criterions.size(); j++) {
                    Criterion criterion = criterions.get(j);
                    if (firstCriterion) {
                        firstCriterion = false;
                    } else {
                        sb.append(" and ");
                    }

                    if (criterion.isNoValue()) {
                        sb.append(criterion.getCondition());
                    } else if (criterion.isSingleValue()) {
                        if (criterion.getTypeHandler() == null) {
                            sb.append(String.format(parmPhrase1, criterion.getCondition(), i, j));
                        } else {
                            sb.append(String.format(parmPhrase1_th, criterion.getCondition(), i, j, criterion.getTypeHandler()));
                        }
                    } else if (criterion.isBetweenValue()) {
                        if (criterion.getTypeHandler() == null) {
                            sb.append(String.format(parmPhrase2, criterion.getCondition(), i, j, i, j));
                        } else {
                            sb.append(String.format(parmPhrase2_th, criterion.getCondition(), i, j, criterion.getTypeHandler(), i, j, criterion.getTypeHandler()));
                        }
                    } else if (criterion.isListValue()) {
                        sb.append(criterion.getCondition());
                        sb.append(" (");
                        List<?> listItems = (List<?>) criterion.getValue();
                        boolean comma = false;
                        for (int k = 0; k < listItems.size(); k++) {
                            if (comma) {
                                sb.append(", ");
                            } else {
                                comma = true;
                            }
                            if (criterion.getTypeHandler() == null) {
                                sb.append(String.format(parmPhrase3, i, j, k));
                            } else {
                                sb.append(String.format(parmPhrase3_th, i, j, k, criterion.getTypeHandler()));
                            }
                        }
                        sb.append(')');
                    }
                }
                sb.append(')');
            }
        }

        if (sb.length() > 0) {
            sql.WHERE(sb.toString());
        }
    }
}